<?php
namespace app\service\MessageParser;

/**
 * MQTTX协议消息解析器
 * 解析新的MQTTX MQTT消息格式
 */
class Vendor2MessageParser implements MessageParserInterface
{
    /**
     * 解析器名称
     */
    private const PARSER_NAME = 'Vendor2 (MQTTX) Message Parser';

    /**
     * 解析器版本
     */
    private const PARSER_VERSION = '1.0';

    /**
     * 判断是否能处理该消息
     * Vendor2协议的特征：主题格式为 rziot/zftx_w06/{IMEI}/result
     *
     * @param string $topic MQTT主题
     * @param array $messageData 消息数据
     * @return bool
     */
    public function canHandle(string $topic, array $messageData): bool
    {
        // 检查主题是否符合Vendor2格式：rziot/zftx_w06/{IMEI}/result
        $isVendor2Topic = strpos($topic, 'rziot/zftx_w06/') === 0 &&
                         strpos($topic, '/result') !== false;

        return $isVendor2Topic;
    }

    /**
     * 解析消息
     *
     * @param string $topic MQTT主题
     * @param array $messageData 消息数据
     * @param string $deviceId 设备标识
     * @return array|null
     */
    public function parse(string $topic, array $messageData, string $deviceId = ''): ?array
    {
        try {
            // 从主题中提取IMEI: rziot/zftx_w06/{IMEI}/result
            $imei = $this->extractImeiFromTopic($topic);

            // 构建保存数据
            $dbm = $messageData['dbm'] ?? 0;
            $dbmInt = intval($dbm);

            $saveData = [
                'IMEI' => $imei,
                'mac' => $imei,
                'iccid' => $messageData['iccid'] ?? '',
                'signal_strength' => $this->getSignalStrength($dbm),
                'mnc' => $this->getMncType($messageData['opname'] ?? ''),
                'ssid' => $messageData['ssid'] ?? '',
                'key' => $messageData['password'] ?? '',
                'main_sim' => $messageData['simSwitch'] ?? 0,
                'user_sim' => $messageData['simSwitch'] ?? 0,
                'band' => $this->getBandType($messageData),
                'hidden_ssid' => $messageData['hidden'] ?? 0,
                'conn_cnt' => $messageData['count'] ?? 0,
                'remain_pwr' => 100, // MQTTX协议未提供电池信息
                'dbm' => $dbmInt,
                'update_time' => date('Y-m-d H:i:s'),
            ];

            return $saveData;

        } catch (\Throwable $e) {
            return null;
        }
    }

    /**
     * 从主题中提取IMEI
     * 主题格式：rziot/zftx_w06/{IMEI}/result
     *
     * @param string $topic MQTT主题
     * @return string IMEI
     */
    private function extractImeiFromTopic(string $topic): string
    {
        // 主题格式：rziot/zftx_w06/{IMEI}/result
        $pattern = '/rziot\/zftx_w06\/([^\/]+)\/result/';
        if (preg_match($pattern, $topic, $matches)) {
            return $matches[1];
        }
        return '';
    }

    /**
     * 根据dBm值获取信号强度等级
     * dBm范围：-120 ~ 0
     * 等级：1-5
     *
     * 处理异常值：
     * - 如果dBm值超出正常范围（< -120 或 > 0），返回默认值3
     */
    private function getSignalStrength($dbm): int
    {
        // 转换为整数，处理字符串输入
        $dbm = intval($dbm);

        // 检查异常值：dBm应该在-120到0之间
        if ($dbm < -120 || $dbm > 0) {
            return 3; // 返回中等信号
        }

        if ($dbm >= -50) {
            return 5; // 极好
        } elseif ($dbm >= -70) {
            return 4; // 好
        } elseif ($dbm >= -85) {
            return 3; // 中等
        } elseif ($dbm >= -100) {
            return 2; // 弱
        } else {
            return 1; // 极弱
        }
    }

    /**
     * 获取运营商类型
     * MQTTX使用运营商代码：46001/46002/46003
     */
    private function getMncType(string $opname): string
    {
        $opcodeMap = [
            '46001' => '移动',
            '46002' => '电信',
            '46003' => '联通',
        ];
        return $opcodeMap[$opname] ?? '未知';
    }

    /**
     * 获取频段类型
     * 根据WiFi状态判断
     */
    private function getBandType(array $messageData): int
    {
        $status = $messageData['status'] ?? 0;
        $status5g = $messageData['status_5g'] ?? 0;

        if ($status && $status5g) {
            return 3; // 2.4G + 5G
        } elseif ($status5g) {
            return 2; // 仅5G
        } elseif ($status) {
            return 1; // 仅2.4G
        } else {
            return 0; // 关闭
        }
    }

    /**
     * 获取解析器名称
     */
    public function getName(): string
    {
        return self::PARSER_NAME;
    }

    /**
     * 获取解析器版本
     */
    public function getVersion(): string
    {
        return self::PARSER_VERSION;
    }
}

